using System;
using System.Data;
using System.IO;
using Agile.Common;

namespace Agile.Genie.Descriptors
{
    /// <summary>
    /// Summary description for VisualStudioProjectFile2003.
    /// </summary>
    public class VisualStudioProjectFile2003 : VisualStudioProjectFile
    {
        #region Constructors and Factories

        /// <summary>
        /// Construct with a project file.
        /// </summary>
        /// <param name="projectFile">The project file to instantiate with.</param>
        protected VisualStudioProjectFile2003(FileInfo projectFile)
            : base(projectFile)
        {
            if (VisualStudioVersion != "2003")
                throw new AgileCommonException("Project file is not a VS2003 project file.");
        }

        /// <summary>
        /// Instantiate a new VisualStudioProjectFile with the given project file.
        /// </summary>
        /// <param name="projectFile">The project file to instantiate with.</param>
        /// <returns></returns>
        public static VisualStudioProjectFile2003 Build(FileInfo projectFile)
        {
            return new VisualStudioProjectFile2003(projectFile);
        }

        /// <summary>
        /// Instantiate a new VisualStudioProjectFile with the path to a project file.
        /// </summary>
        /// <param name="projectFilePath">The path of a project file.</param>
        /// <returns></returns>
        public static VisualStudioProjectFile2003 Build(string projectFilePath)
        {
            return Build(new FileInfo(projectFilePath));
        }

        #endregion

        #region Overrides

        private DataTable _projectReferenceRows2003;

        /// <summary>
        /// Gets the path (including the application name) of the visual studio
        /// version that needs to be used to open the project file.
        /// </summary>
        public override string VisualStudioApplicationPath
        {
            get { return @"C:\Program Files\Microsoft Visual Studio .NET 2003\Common7\IDE\devenv.exe"; }
        }


        /// <summary>
        /// Gets the Assembly name of the project.
        /// </summary>
        public override string ProjectAssemblyName
        {
            get { return ProjectFileData.Tables["Settings"].Rows[0]["AssemblyName"].ToString(); }
        }

        /// <summary>
        /// Gets the projects GUID.
        /// </summary>
        public override Guid ProjectGuid
        {
            get { return new Guid(ProjectFileData.Tables["CSHARP"].Rows[0]["ProjectGuid"].ToString()); }
        }

        /// <summary>
        /// Gets the type of project, e.g. Web or Local
        /// </summary>
        public override string PlatformFamilyName
        {
            get
            {
                if (!ProjectFileData.Tables["CSHARP"].Columns.Contains("PlatformFamilyName"))
                    return string.Empty;

                return ProjectFileData.Tables["CSHARP"].Rows[0]["PlatformFamilyName"].ToString();
            }
        }

        /// <summary>
        /// Gets the projects output type, e.g. Exe or library
        /// </summary>
        public override string OutputType
        {
            get { return ProjectFileData.Tables["Settings"].Rows[0]["OutputType"].ToString(); }
        }

        /// <summary>
        /// Gets the rows from the dataset that relate specifically to references to 
        /// other projects.
        /// </summary>
        protected override DataTable ProjectReferenceRows
        {
            get
            {
                if (_projectReferenceRows2003 == null)
                {
                    _projectReferenceRows2003 = ProjectFileData.Tables["Reference"].Copy();

                    if (!_projectReferenceRows2003.Columns.Contains("Project"))
                        return new DataTable("NoProjectFilesReferenced");

                    // Now remove all rows that are references to .dll's
                    for (int i = (_projectReferenceRows2003.Rows.Count - 1); i > -1; i--)
                    {
                        object project = _projectReferenceRows2003.Rows[i]["Project"];
                        if (project == DBNull.Value)
                            _projectReferenceRows2003.Rows.RemoveAt(i);
                    }
                }
                return _projectReferenceRows2003;
            }
        }

        /// <summary>
        /// Gets the Assembly name from the given Reference table row.
        /// Looks for the "Name" column, not the AssemblyName column.
        /// </summary>
        /// <param name="referenceTableRow">A row from the Reference table.</param>
        /// <returns></returns>
        public override string GetReferencedAssemblyName(DataRow referenceTableRow)
        {
            object name = referenceTableRow["Name"];
            if (name == DBNull.Value)
                return string.Empty;
            return name.ToString();
        }

        #endregion
    }
}